/***************************************************************************\
 * The Mattise Kernel														*
 * Copyright 2007 Matthew Iselin											*
 * Licensed under the GPL													*
 *																			*
 * reloc.cc																	*
 *																			*
 * Relocation superclass, all relocations need to be done in terms of this	*
 * class																	*
 *																			*
\***************************************************************************/

// Includes
#include <system.h>
#include <stdio.h>
#include <reloc.h>
#include <memory.h>
#include <string.h>
#include <filesys.h>
#include <pm.h>
#include <paging.h>

// Class Definition

/// Relocation constructor
Relocation::Relocation()
{
}

/// Relocation destructor
Relocation::~Relocation()
{
	// close the file
	fclose( fp );
	kfree( fileName );
}

/// Loads the file and maps its physical data appropriately
bool Relocation::LoadFile( const char* fn )
{	
	// copy the filename
	fileName = (char*) kmalloc( strlen( fn ) + 1 );
	memset( fileName, 0, strlen( fn ) + 1 );
	strcpy( fileName, fn );
	
	// open the file
	fp = fopen( fn, "rw" );
	
	// check for a valid file
	if( fp == -1 )
		return false;
	
	// divide the space into pages
	uint_t pagecount = ( fsize( fp ) / 4096 ) + 1;
	
	// allocate them
	uint_t physbase = (uint_t) pm_alloc( pagecount );
	
	// map them
	for( int i = 0; i < pagecount; i++ )
	{
		// map it
		MapPhysicalAddress( GetKernelPageDir(), physbase + (i*0x1000), physbase + (i*0x1000), PF_PRESENT | PF_READWRITE | PF_SUPERVISOR );
	}
	
	// now read it in
	fileData = (char*) physbase;
	fseek( fp, 0, SEEK_SET );
	fread( fileData, 1, fsize( fp ), fp );
	
	// ready to go
	return true;
}

/// Loads from a position in memory (ie. already loaded the data)
bool Relocation::LoadFile( const int addr )
{
	// fill it in
	fileData = (char*) addr;
}

/// Gets the base of the file
uint_t Relocation::GetBase()
{
	// gets the address of the buffer
	return (uint_t) fileData;
}
